package com.hoshiicloud.saleorder.service.impl.customer;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hoshiicloud.common.aop.Logable;
import com.hoshiicloud.common.exception.CommonError;
import com.hoshiicloud.common.exception.ServiceException;
import com.hoshiicloud.common.rpc.Response;
import com.hoshiicloud.common.utils.BeanUtils;
import com.hoshiicloud.saleorder.dto.SkuDTO;
import com.hoshiicloud.saleorder.feign.GoodsService;
import com.hoshiicloud.saleorder.feign.IdGeneratorService;
import com.hoshiicloud.saleorder.mapper.customer.CartMapper;
import com.hoshiicloud.saleorder.param.customer.CartDeleteParam;
import com.hoshiicloud.saleorder.service.customer.ICartService;
import com.hoshiicloud.user.entity.customer.Cart;
import com.hoshiicloud.user.entity.customer.ExtSku;
import com.hoshiicloud.user.vo.customer.CartVO;
import java.math.RoundingMode;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

/**
 * <p>
 * 购物车购物信息记录表 服务实现类
 * </p>
 *
 * @author Mr.Wu
 * @since 2019-04-28
 */
@Service
@Slf4j
public class CartServiceImpl extends ServiceImpl<CartMapper, Cart> implements ICartService {

    @Autowired
    private CartMapper cartMapper;

    @Autowired
    private IdGeneratorService idGeneratorService;

    @Autowired
    private GoodsService goodsService;


    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-新增购物车购物信息记录表信息")
    public Response insert(Cart param) {
        // TODO 判断用户是否存在
        String id = null;
        Long buyQuantity = param.getGoodsQuantity();
        Cart findParam = new Cart();
        findParam.setUserId(param.getUserId());
        findParam.setSkuId(param.getSkuId());
        QueryWrapper<Cart> queryWrapper = new QueryWrapper<>(findParam);
        Cart data = cartMapper.selectOne(queryWrapper);

        Response<SkuDTO> result = goodsService.getSkuInfoExtSku(param.getSkuId());
        if (result == null || !result.isSuccess()) {
            throw new ServiceException("商品服务失败");
        }
        SkuDTO good = result.getData();
        if (good == null) {
            throw new ServiceException(("商品不存在"));
        }

        if (data != null) {
            //商品已在购物车，进行更新操作
            data.setUpdatedtime(LocalDateTime.now());
            if (2 != (good.getStatus())) {
                //商品未处于上架状态
                data.setStatus(0);
                cartMapper.updateById(data);
                return Response.failed("商品已下架");
            }
            //写入测试属性
            data.setSkuExtendProp(good.getExtendProperty());
            data.setGoodsPrice(good.getGoodsPrice());
            data.setSpuExtendSpec(good.getExtendSpec());
            data.setSkuTitle(good.getSkuTitle());
            data.setSpuTitle(good.getSpuTitle());
            data.setSkuImage(good.getSkuImage());
            data.setGoodsQuantity(data.getGoodsQuantity() + buyQuantity);
        } else {
            id = idGeneratorService.queryGeneratorId();
            if (StringUtils.isBlank(id)) {
                throw new ServiceException(CommonError.error("id服务失败"));
            }

            if (2 != (good.getStatus())) {
                //商品未处于上架状态
                return Response.failed("商品已下架");
            }
            //新增购物车
            data = param;
            data.setPlatformId(good.getPlatformId());
            data.setStoreId(good.getStoreId());
            data.setSkuExtendProp(good.getExtendProperty());
            data.setSpuId(good.getSpuId());
            data.setSkuId(good.getExtSkuId());
            data.setGoodsPrice(good.getGoodsPrice());
            data.setSpuExtendSpec(good.getExtendSpec());
            data.setSkuTitle(good.getSkuTitle());
            data.setSpuTitle(good.getSpuTitle());
            data.setSkuImage(good.getSkuImage());
            data.setRecId(Long.parseLong(id));
            data.setCreatedtime(LocalDateTime.now());
        }
        //设置购物车删除状态
        data.setDeleted(0);
        //判断超库存属性，如果允许超库存则不做检查
        //不允许超库存下单，固定判断
        if (true) {
            //检查库存
            Long availableStock = good.getQuantity().subtract(good.getFreezes())
                    .setScale(0, RoundingMode.DOWN).longValue();
            if (data.getGoodsQuantity().compareTo(availableStock) == 1) {
                return Response.failed("库存不足");
            }
        }
        boolean success = this.saveOrUpdate(data);
        if (!success) {
            throw new ServiceException(CommonError.error("新增失败"));
        }
        //TODO 查询到的图片地址拼接上动态获取到的域名
        //此处暂时写死
//        String url = "https://zyc-yanxuan.oss-cn-hangzhou.aliyuncs.com/images/";
        data.setSkuImage(data.getSkuImage());
        return Response.data(data);


    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-修改购物车购物信息记录表信息")
    public Response updateDataById(Cart param) {
        // 前台修改数量,提交订单时或调用刷新信息时才检查商品数量
        int count = cartMapper.updateById(param);
        if (count <= 0) {
            throw new ServiceException(CommonError.error("修改失败"));
        }
        return Response.success("修改成功");
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-删除购物车购物信息记录表信息")
    public Response deleteDataByNumber(CartDeleteParam param) {
        Cart cart = cartMapper.selectById(param.getId());
        if (cart == null) {
            throw new ServiceException(CommonError.error("删除失败"));
        }
        //删除部分数量的情况下不更改购物车状态
        if (param.getGoodsQuantity() < cart.getGoodsQuantity()) {
            cart.setGoodsQuantity(cart.getGoodsQuantity() - param.getGoodsQuantity());
        } else {
            cart.setGoodsQuantity(0L);
            //逻辑删除
            cart.setDeleted(1);
        }
        cart.setUpdatedtime(LocalDateTime.now());
        //int count = cartMapper.deleteById(id);
        int count = cartMapper.updateById(cart);
        if (count <= 0) {
            throw new ServiceException(CommonError.error("删除失败"));
        } else {
            return Response.success("删除成功");
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-删除购物车购物信息记录表信息")
    public Response deleteDataById(String id) {
        //逻辑删除
        Cart entity = new Cart();
        entity.setRecId(Long.valueOf(id));
        entity.setDeleted(1);
        entity.setGoodsQuantity(0L);
        entity.setUpdatedtime(LocalDateTime.now());
        //int count = cartMapper.deleteById(id);
        int count = cartMapper.updateById(entity);
        if (count <= 0) {
            throw new ServiceException(CommonError.error("删除失败"));
        } else {
            return Response.success("删除成功");
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-删除购物车购物信息记录表信息")
    public Response deleteDataByIds(List<Long> ids) {
        //逻辑删除
        UpdateWrapper updateWrapper = new UpdateWrapper();
        Cart entity = new Cart();
        entity.setDeleted(1);
        entity.setGoodsQuantity(0L);
        entity.setUpdatedtime(LocalDateTime.now());
        updateWrapper.in("rec_id", ids);
        int count = cartMapper.update(entity, updateWrapper);
        if (count <= 0) {
            throw new ServiceException(CommonError.error("删除失败"));
        } else {
            return Response.success("删除成功");
        }
    }

    @Override
    @Cacheable(cacheNames = "Cart", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+#id")
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-查询购物车购物信息记录表信息详情")
    public Response getDetail(String id) {
        Cart data = cartMapper.selectById(id);
        if (data == null) {
            return Response.failed("数据不存在");
        } else {
            return Response.data(data);
        }
    }

    @Override
    // @Cacheable(cacheNames = "Cart", key = "T(com.hoshiicloud.common.utils.DigestUtils).md5('key=' + #key + ')')")
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-查询购物车购物信息记录表信息列表")
    public Response<List<CartVO>> getList(QueryWrapper<Cart> queryWrapper, String key) {
        UpdateWrapper<Cart> cartUpdateWrapper = new UpdateWrapper<>();
        cartUpdateWrapper.getSqlSegment();
        queryWrapper.getSqlSegment();
        List<Cart> list = cartMapper.selectList(queryWrapper);
        List<CartVO> voList = new ArrayList<>(10);
        //TODO 自定义sql查询,查询到的图片地址拼接上域名
        //此处暂时写死
//        String url = "https://zyc-yanxuan.oss-cn-hangzhou.aliyuncs.com/images/";
        if (CollectionUtils.isNotEmpty(list)) {
            list.forEach(cart -> {
                CartVO cartVO = new CartVO();
                BeanUtils.copyProperties(cart, cartVO);
                cartVO.setSkuImage(cart.getSkuImage());
                // 将json字符串转换成Map
                Map<String, Object> specMap = JSON.parseObject(cart.getSpuExtendSpec(), Map.class);
                cartVO.setSpuExtendSpec(specMap);
                voList.add(cartVO);
            });
        }
        //
        // for (int i = 0; i < list.size(); i++) {
        //     CartVO vo = new CartVO();
        //     BeanUtils.copyProperties(list.get(i), vo);
        //     vo.setSkuImage(vo.getSkuImage());
        //     Map<String, Object> specMap = null;
        //     //json字符串先转换为map对象再返回前端
        //     specMap = JSONObject.parseObject(list.get(i).getSpuExtendSpec(), Map.class);
        //     vo.setSpuExtendSpec(specMap);
        //     voList.add(vo);
        // }
        return Response.data(voList);
    }

    @Override
    @Cacheable(cacheNames = "Cart", key = "#root.targetClass.simpleName+':'+#root.methodName+':'+T(com.hoshiicloud.common.utils.DigestUtils).md5(#key)")
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-分页查询购物车购物信息记录表信息")
    public Response<IPage<CartVO>> getPage(IPage<Cart> page, QueryWrapper<Cart> queryWrapper,
            String key) {
        IPage<Cart> cartPage = cartMapper.selectPage(page, queryWrapper);
        List<Cart> list = cartPage.getRecords();
        List<CartVO> voList = new ArrayList<>();
        IPage<CartVO> cartVoPage = new Page<>();
        BeanUtils.copyProperties(cartPage, cartVoPage);
        //TODO 自定义sql查询,查询到的图片地址拼接上域名
        //此处暂时写死
//        String url = "https://zyc-yanxuan.oss-cn-hangzhou.aliyuncs.com/images/";
        for (int i = 0; i < list.size(); i++) {
            CartVO vo = new CartVO();
            BeanUtils.copyProperties(list.get(i), vo);
            vo.setSkuImage(vo.getSkuImage());
            Map<String, Object> specMap = null;
            //json字符串先转换为map对象再返回前端
            specMap = JSONObject.parseObject(list.get(i).getSpuExtendSpec(), Map.class);
            vo.setSpuExtendSpec(specMap);
            voList.add(vo);
        }
        cartVoPage.setRecords(voList);
        return Response.data(cartVoPage);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-更新购物车购物信息有效信息")
    public Response updateCartInfo(QueryWrapper<Cart> queryWrapper) {

        List<Cart> cartList = cartMapper.selectList(queryWrapper);
        // 组装商品ID列表
        List<Long> idList = new ArrayList<Long>();
        for (Cart cart : cartList) {
            idList.add(cart.getSkuId());
        }
        Response<List<ExtSku>> result = goodsService.getGoodsDetailByIds(idList);
        if (!result.isSuccess()) {
            //服务调用失败,返回服务抛出的异常信息
            return result;
        }
        List<ExtSku> goodsList = result.getData();
        boolean isPriceChange = false;

        //转为map进行处理
        Map<Long, ExtSku> goodsMap = new HashMap<Long, ExtSku>();
        List<Cart> updateList = new ArrayList<Cart>();
        for (int i = 0; i < goodsList.size(); i++) {
            goodsMap.put(goodsList.get(i).getId(), goodsList.get(i));
        }
        for (int j = 0; j < cartList.size(); j++) {
            Cart item = cartList.get(j);
            ExtSku good = goodsMap.get(item.getSkuId());
            if (good == null || 2 != good.getStatus()) {
                //如果商品不存在或商品已经下架更新状态为失效
                item.setStatus(0);
                item.setUpdatedtime(LocalDateTime.now());
                updateList.add(item);
            } else if (item.getGoodsPrice().compareTo(good.getSalePrice()) != 0) {
                //如果商品信息发生变动,更新
                //暂时只对价格处理
                item.setGoodsPrice(good.getSalePrice());
                item.setUpdatedtime(LocalDateTime.now());
                updateList.add(item);
                isPriceChange = true;
            }
            if (updateList.size() > 0) {
                saveOrUpdateBatch(updateList);
                if (isPriceChange) {
                    return Response.success("价格已更新");
                } else {
                    return Response.success("商品已过期");
                }
            }
        }
        // TODO 更新商品价格,如果价格发生变动返回对应的结果,商品如下架更新购物车状态为失效
        return Response.success("更新成功");
    }

    /**
     * @param entityList
     * @return boolean
     * @author: Mr.wu
     * @descripton: 批量保存或更新
     * @date: 19:04 2019/5/21
     */
    @Override
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    public boolean saveOrUpdateBatch(Collection<Cart> entityList) {
        return super.saveOrUpdateBatch(entityList);
    }

    @Override
    @Cacheable(cacheNames = "Cart", key = "T(com.hoshiicloud.common.utils.DigestUtils).md5('Wrapper(SqlSelect=' + #queryWrapper.getSqlSelect() + ', SqlSegment=' + #queryWrapper.getSqlSegment() + ')')")
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-查询购物车数量")
    public Integer getCount(QueryWrapper<Cart> queryWrapper) {
        return cartMapper.selectCount(queryWrapper);
    }

    /**
     * 根据店铺ID批量删除购物车信息
     *
     * @param storeId 店铺ID
     * @return Response
     * @author yangcheng
     */
    @Transactional(rollbackFor = Exception.class)
    @CacheEvict(cacheNames = {"Cart"}, allEntries = true)
    @Logable(authName = "前台用户操作-购物车购物信息记录表信息管理-根据用户ID和店铺ID批量删除购物车信息")
    @Override
    public Response deleteByUserIdAndStoreId(Long userId, Long storeId) {
        //逻辑删除
        UpdateWrapper updateWrapper = new UpdateWrapper();
        Cart entity = new Cart();
        entity.setDeleted(1);
        entity.setGoodsQuantity(0L);
        entity.setUpdatedtime(LocalDateTime.now());
        updateWrapper.eq("user_id", userId);
        updateWrapper.eq("store_id", storeId);
        int count = cartMapper.update(entity, updateWrapper);
        if (count <= 0) {
            throw new ServiceException(CommonError.error("删除失败"));
        } else {
            return Response.success("删除成功");
        }
    }

}
